#ifndef _INCLUDE_OPENNETWORK_I_NETWORK_PORT_
#define _INCLUDE_OPENNETWORK_I_NETWORK_PORT_

/*!
    Copright: Kai "DrHalan" Mast - www.freakybytes.org

    This file is part of OpenNetwork. See OpenNetwork.h for license information.
*/


#include "types.h"
#include "ESendMessageResult.h"
#include "EPortType.h"
#include "EFeatureType.h"
#include "SNetworkAddress.h"
#include "INetworkCallback.h"

namespace onet
{

class INetworkPort
{
    public:
        INetworkPort(INetworkCallback* callback_, u16 maxPeers_, u16 portNumber_, bool listening_, bool IPv6_) : callback(callback_), maxPeers(maxPeers_), portNumber(portNumber_), listening(listening_), IPv6(IPv6_)
        {
            callback->onCreate(this);
        }

        virtual ~INetworkPort(void)
        {
            callback->onDestroy();
        }

        //! Gets the callback
        INetworkCallback* getCallback(void)
        {
            return callback;
        }

        //! Gets the used (listening) port number
        u16 getPortNumber(void) const
        {
            return portNumber;
        }

        //! Get the maximum numbers of possible peers
        u16 getMaxPeers(void) const
        {
            return maxPeers;
        }

        //! States if the port is an IPv6 port
        bool isIPv6(void) const
        {
            return IPv6;
        }

        //! Is the port listening for new connections?
        bool isListening(void) const
        {
            return listening;
        }

        //! Initialization function
        virtual bool init() = 0;

        //! Connect to an address
        //! Returns false if already connected
        virtual bool connect(const SNetworkAddress& address) = 0;

        //! The disconnect pendant
        //! Returns false if the peerID is invalid
        virtual bool disconnect(const PeerID id) = 0;

        //! Disconnects all peers
        //! Returns number of peers disconnected
        virtual u16 disconnectAll(void) = 0;

        //! Gets the address (IP/Port) of a peer
        virtual SNetworkAddress getAddress(const PeerID id) = 0;

        //! Get the latency of a peer
        virtual s32 getLatency(const PeerID id)= 0;

        //! Looks up if a certain address is connected
        virtual bool isConnected(const SNetworkAddress& a) = 0;

        //! Gets the Id of a certain address
        virtual PeerID getPeer(const SNetworkAddress& a) = 0;

        //! Sends and receives data
        virtual void work(void) = 0;

        //! Get the protocol used
        virtual EPortType getType() const = 0;

        //! Send data to peer - Reliable or not
        virtual ESendMessageResult send(const PeerID id, const c8 type, const u16 length, const c8* data, const bool reliable) = 0;

        //! Send data to address (Raw)
        virtual ESendMessageResult sendRaw(const SNetworkAddress& address, const u16 length, const c8* data) = 0;

        //! Query certain features
        virtual bool hasFeature(EFeatureType type) const = 0;

        //! Returns number of peers connected
        virtual u16 getPeerCount() = 0;

    protected:
        //! The callback used for all events etc
        INetworkCallback* callback;

        //! The amount of connections possible
        u16 maxPeers;

        //! The port used
        u16 portNumber;

        //! Listen Flag
        bool listening;

        //! Is uning IPv6?
        bool IPv6;
};

} //!end namespace onet

#endif
